﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using CocoaAni.Net.WebSockets.Server.ArgAdapters.Base;
using CocoaAni.Net.WebSockets.Server.Exceptions;

namespace CocoaAni.Net.WebSockets.Server;

public class MessageHandlerArgsBuilder
{
    public MessageHandlerArgsBuilder(Dictionary<Type, IMessageArgAdapter> adapters)
    {
        Adapters = adapters;
    }
    public Dictionary<Type, IMessageArgAdapter> Adapters { get; set; }

    public object?[] BuildArgs(WebSocketContext context)
    {
        context.MessageArgContext.Reset();
        var handlerInfo = context.MessageHandlerInfo;
        var argInfos = handlerInfo.ArgInfos;
        var args = new object?[argInfos.Length];
        for (var i = 0; i < argInfos.Length; i++)
        {
            var argInfo = argInfos[i];
            if (argInfo.Adapter == null)
            {
                if (argInfo.AdapterRegisterAttributeType != null)
                {
                    if (!Adapters.ContainsKey(argInfo.AdapterRegisterAttributeType))
                    {
                        throw new WebSocketServiceException
                            ($"NotFoundMessageArgAdapter For [{argInfo.Name}] ByRegisterAttributesType={argInfo.AdapterRegisterAttributeType}! Path={context.ControllerAndHandlerPath}");
                    }
                    argInfo.Adapter = Adapters[argInfo.AdapterRegisterAttributeType];
                }
                else
                {
                    if (!Adapters.ContainsKey(argInfo.Type))
                    {
                        throw new WebSocketServiceException
                            ($"NotFoundMessageArgAdapter For [{argInfo.Name}] Type={argInfo.Type}!  Path={context.ControllerAndHandlerPath}");
                    }
                    argInfo.Adapter = Adapters[argInfo.Type];
                }
            }
            context.MessageArgContext.SetNextArgInfo(argInfo);
            args[i] = argInfo.Adapter.GetTargetParameter(context.MessageArgContext);
        }
        return args;
    }
}